/*******************************************************************************
 * FilePath    : \Software\Examples_Ble_MS1656\ble_app_peripheral_uart\Src\User\User_Key.c
 * Version     : 1.0
 * Brief       : 
 * Author      : AndrewHu
 * Company     : Shanghai MacroGiga Electronics CO.,Ltd
 * Email       : Hubinbo@macrogiga.com
 * Date        : 2020-04-03 15:15:31
 * LastEditors : AndrewHu
 * LastEditTime: 2021-05-08 19:29:41
 * Description : 
 ******************************************************************************/

/* Includes ------------------------------------------------------------------*/
#include <Includes.h>
/* Private typedef -----------------------------------------------------------*/
/* Private define ------------------------------------------------------------*/
#define ScanTime 10                         //扫描间隔时间(ms)
#define DebounceTime 30                     //去抖动时间(ms)
#define DebounceT (DebounceTime / ScanTime) //按键去抖
#define TimesDebounce (200 / ScanTime)      //连按判断
#define LongDebounce (2000 / ScanTime)      //长按判断
/* Private macro -------------------------------------------------------------*/
/* Private variables ---------------------------------------------------------*/
//
u8 key_flag = 0x00;
u8 key_delay = 0x00;
u8 key_Times_delay = 0x00;
u16 key_Long_delay = 0x00;
/* Private function ----------------------------------------------------------*/
/* extern --------------------------------------------------------------------*/
/*******************************************************************************
 * Function    : GetKeyPinStatus
 * Brief       : 判断按键引脚状态
 * Parameter   : 
 * Returns     : 
 * Date        : 2020-04-17 16:47:55
 * Description : 按键按下时不进入低功耗
 ******************************************************************************/
u8 GetKeyStatus(void)
{
    if ((getKeyPinStatus()) || (key_flag != 0x00))
        return 1; //按键需要处理
    else
        return 0;
}
/*******************************************************************************
 * Function    : Key_Scan
 * Brief       : 按键扫描
 * Parameter   : 
 * Returns     : 
 * Date        : 2020-04-03 16:30:17
 * Description : bit7-按键状态改变标志位，bit4-按键状态标志位
 ******************************************************************************/
u8 Key_Scan(void)
{
    if (getKeyPinStatus())
    {
        if ((key_flag & KeyFlag_down) != 0x00)
            key_delay = 0x00;
    }
    else
    {
        if ((key_flag & KeyFlag_down) == 0x00)
            key_delay = 0x00;
    }
    //按下判断
    key_delay++;
    if (key_delay >= DebounceT)
    {
        key_delay = 0x00;
        key_Times_delay = 0x00; //连按判断计时
        key_Long_delay = 0x00;  //长按判断计时

        if ((key_flag & KeyFlag_down) == 0x00)
        {
            //按键按下
            key_flag |= KeyFlag_down;

            if ((key_flag & KeyFlag_times) == 0x00) //连按判断
                key_flag &= 0xf0;                   //非连按状态，按下次数清零

            if ((key_flag & 0x07) < 0x07)
                key_flag++; //连按次数累计
        }
        else
        {
            //按键松开
            key_flag &= ~KeyFlag_down;
        }
        key_flag |= KeyFlag_times; //使能连按判断

        key_flag |= KeyFlag_event;
        return key_flag;
    }
    //连按判断
    if ((key_flag & KeyFlag_times) != 0x00)
    {
        key_Times_delay++;
        if (key_Times_delay >= TimesDebounce)
        {
            key_Times_delay = 0x00;
            key_flag &= 0xf0; //清除连按次数
            key_flag &= ~KeyFlag_Long;
        }
    }
    //长按判断
    if ((key_flag & (KeyFlag_down | KeyFlag_Long)) == KeyFlag_down)
    {
        key_Long_delay++;
        if (key_Long_delay >= LongDebounce)
        {
            key_Long_delay = 0x00;
            key_flag |= KeyFlag_Long;
            key_flag |= KeyFlag_event;
            return key_flag;
        }
    }
    return 0;
}
/*******************************************************************************
 * Function    : Key_ClearFlag
 * Brief       : 清除按键事件旗标
 * Parameter   : 
 * Returns     : 
 * Date        : 2020-04-04 15:12:17
 * Description : 
 ******************************************************************************/
void Key_ClearFlag(void)
{
    key_flag &= ~KeyFlag_event;
}
/*******************************************************************************
 * Function    : GetKeyFlag
 * Brief       : 获取当前按键状态信息
 * Parameter   : 
 * Returns     : 
 * Date        : 2020-04-04 15:29:46
 * Description : 
 ******************************************************************************/
u8 GetKeyFlag(void)
{
    return key_flag;
}
